parameter_definition(
  build_info_evaluate_targets

  )
function(build_info_evaluate_targets)
  arguments_extract_defined_values(0 ${ARGC} build_info_evaluate_targets)    
  ans(build_infos)
  map_new()
  ans(evaluated_targets)
  foreach(build_info ${build_infos})    
    map_tryget(${build_info} build_parameters)
    ans(build_parameters)

    map_tryget(${build_info} id)
    ans(build_id)

    if(NOT build_parameters)
      fatal("no build parameters specified for build")
      # todo maybe just ignoriung is enough 
    endif()

    ## get the build descriptor template for current build
    map_tryget(${build_info} build_descriptor)
    ans(build_descriptor)

    ## get target templates generated by build
    map_tryget(${build_descriptor} targets)
    ans(build_targets)

    ## a single build info can have multiple targets
    map_template_evaluate_scoped("${build_parameters}" "${build_targets}")
    ans(evaluated_build_targets)

    foreach(evaluated_build_target ${evaluated_build_targets})
      map_tryget("${evaluated_build_target}" name)
      ans(target_name)
      if(NOT target_name)
        set(target_name "default")
        map_set(${evaluated_build_target} name "${target_name}")
      endif()
      map_set(${evaluated_build_target} build_id ${build_id})
      map_set(${evaluated_build_target} build_parameters ${build_parameters})
      map_append(${evaluated_targets} "${target_name}" "${evaluated_build_target}")
    endforeach()

  endforeach()
  return(${evaluated_targets})
endfunction()



  # if(NOT target_namespace)
  #   log("no target namespace is specified - defaulting to package id '${package_id}'")
  #   string_to_target_name("${package_id}")
  #   ans(target_namespace)
  # endif()


parameter_definition(cmake_import_target_from_build_info_targets
  <--target-namespace{"namespace for targets of package handle"}=>target_namespace:<target_identifier>>
  )
function(cmake_import_target_from_build_info_targets)
  arguments_extract_defined_values(0 ${ARGC} cmake_import_target_from_build_info_targets)    
  ans(target_configurations)

  ## targets are only available if in script mode
  cmake_check_configure_mode()


  assign(name = target_configurations[:].name)
  list_unique(name)
  ans(name)
  list(LENGTH name size )
  if(NOT "${size}" STREQUAL "1")
    fatal("all build info targets need to have the same name")
  endif()

  assign(type = target_configurations[:].type)
  list_unique(type)
  ans(type)
  list(LENGTH type size)  
  if(NOT "${size}" STREQUAL "1")
    fatal("all build info targets need to have the same target type")
  endif()




  if(NOT name OR "${name}_" STREQUAL "default_")
    set(cmake_target_name "${target_namespace}")
  else()
    set(cmake_target_name "${target_namespace}::${name}")
  endif()



  foreach(target_configuration ${target_configurations})      
    map_set_default("${target_configuration}" cmake_target_name "${cmake_target_name}")
  endforeach()

  #assign(ids = target_configurations[:].build_id)

  assign(configs  = target_configurations[:].build_parameters.config)
  assign(linkages = target_configurations[:].build_parameters.linkage)

  map_new()
  ans(cmake_target)
  map_set(${cmake_target} name "${cmake_target_name}")
  map_set(${cmake_target} type "${type}")

  # set default values  (default to release config)

  # map_set(${cmake_target} include_dirs)
  # map_set(${cmake_target} library) ## if library == empty -> use name as library name



  # then set release specific values
  foreach(config ${configs})
    map_new()
    ans(config_properties)


    set(build_parameters)
    set(target_configuration)
    foreach(current_target_configuration ${target_configurations})
      map_tryget("${current_target_configuration}" "build_parameters")
      ans(build_parameters)

      map_tryget(${build_parameters} config)
      ans(current_config)

      if("${current_config}_" STREQUAL "${config}_")
        set(target_configuration ${current_target_configuration})
        break()
      endif()
    endforeach()

    if(NOT target_configuration)
      fatal("could not associate config '${config}' with target_configuration config")
    endif()


    map_tryget(${target_configuration} include_dirs)
    ans(include_dirs)
    map_tryget(${target_configuration} output)
    ans(output)
    map_tryget(${target_configuration} libs)
    ans(libs)

    message("parameters for ${config} ######")
    print_vars(build_parameters)
    print_vars(target_configuration)

    map_tryget(${build_parameters} install_dir)
    ans(install_dir)


    map_template_evaluate_scoped("${build_parameters}" "${include_dirs}")
    ans(include_dirs)
    if(include_dirs)
      map_set(${config_properties} include_dirs ${include_dirs})      
    endif()

    map_template_evaluate_scoped("${build_parameters}" "${libs}")
    ans(libs)
    if(libs)
      pushd("${install_dir}")
        glob(${libs})
        ans(library_locations)
      popd()
    endif()

    
    map_template_evaluate_scoped("${build_parameters}" "${output}")
    ans(output)
    if(output)
      pushd("${install_dir}")
        glob(${output})
        ans(output)
        map_set(${config_properties} content_files ${output})
      popd()
    endif()

    #map_set(${config_properties} imported_location ${libs})
    #map_set(${config_properties} imported_implib "")
    #map_set(${config_properties} content_files ${output})
    #map_set(${config_properties} content_files )

    map_keys(${config_properties})
    ans(has_keys)

    if(has_keys)
      map_set(${cmake_target} ${config} ${config_properties})
    endif()


  endforeach()



  map_tryget(${cmake_target} release)
  ans(release_config)


  if(release_config)
    map_defaults(${cmake_target} "${release_config}")
  endif()


  return(${cmake_target})
  

endfunction()

parameter_definition(cmake_target_import
  <--cmake-target{""}=>cmake_target:<map>>
  )
function(cmake_target_import)  
  arguments_extract_defined_values(0 ${ARGC} cmake_target_import)    
  ans(args)

  log("trying to import target {cmake_target.name}")

  map_tryget(${cmake_target} name)
  ans(name)
  map_tryget(${cmake_target} type)
  ans(type)

  if(NOT ("${type}" STREQUAL library) AND NOT ("${type}" STREQUAL "interface"))
    fatal("cannot import cmake target of type '${type}'")
  endif()

  set(scope GLOBAL)
  set(imported IMPORTED)

  set(linkage SHARED) # or STATIC  or INTERFACE

  if("${type}" STREQUAL "interface")
    set(linkage "INTERFACE")  
  endif()

  add_library("${name}" ${linkage} ${imported} ${scope})


  if(imported)

    ## depending on config using generator expression
    target_set("${name}" INTERFACE_INCLUDE_DIRECTORIES ...)


    if("${linkage}" STREQUAL "SHARED")
      target_set("${name}" IMPORTED_LOCATION_<CONFIG>)
      target_set("${name}" IMPORTED_IMPLIB_<CONFIG>)
    elseif("${linkage}" STREQUAL "INTERFACE")

    elseif("${linkage}" STREQUAL "STATIC")
      target_set("${name}" IMPORTED_LOCATION_<CONFIG>)

    endif()

  endif()
  return()

endfunction()
parameter_definition(build_info_targets_import
  <--target-namespace{"namespace for targets of package handle"}=>target_namespace:<target_identifier>>
  )
function(build_info_targets_import)
  arguments_extract_defined_values(0 ${ARGC} build_info_targets_import)    
  ans(build_infos)

  log("trying to import builds to target-namespace '${target_namespace}'")

  build_info_evaluate_targets(${build_infos})
  ans(evaluated_targets)

  if(NOT evaluated_targets)
    fatal("could not evaluated targets")
  endif()

  map_keys(${evaluated_targets})
  ans(package_target_names)

  set(cmake_target)
  foreach(package_target_name ${package_target_names})
    map_tryget(${evaluated_targets} "${package_target_name}")
    ans(target_configurations)

    cmake_import_target_from_build_info_targets("${target_namespace}" ${target_configurations})
    ans_append(cmake_targets)




  endforeach()

  foreach(cmake_target ${cmake_targets})
    cmake_target_import(${cmake_target})
  endforeach()

  return_ref(cmake_targets)




  # set(bin_dir bin)
  # set(lib_dir lib)


  # set(include_dirs)
  # set(implib)
  # set(location)
  # set(configs)

  #   map_tryget(${build_parameters} install_dir)
  #   ans(install_dir)

  #   set(include_dir include)



  #   map_tryget("${build_parameters}" config)
  #   ans(cfg)   
  #   string_toupper("${cfg}")
  #   ans(cfg)
  #   list(APPEND configs "${cfg}")

  #   glob("${install_dir}/${bin_dir}/*${CMAKE_SHARED_MODULE_SUFFIX}")
  #   ans(shared_lib)


  #   glob("${install_dir}/${lib_dir}/*${CMAKE_STATIC_LIBRARY_SUFFIX}")
  #   ans(static_lib)

    
  #   set(include_dirs ${include_dirs} "$<$<CONFIG:${cfg}>:${install_dir}/${include_dir}>")


  #   if(shared_lib)
  #     if(NOT location)
  #       map_new()
  #       ans(location)
  #     endif()
  #     list(LENGTH shared_lib nLibs)
  #     if("${nLibs}" GREATER 1)
  #       message(FATAL_ERROR "cannot handle shared nlibs greater 1")
  #     endif()
  #     map_set("${location}" "${cfg}" "${shared_lib}")
  #   endif()

  #   if(static_lib)
  #     if(NOT implib)
  #       map_new()
  #       ans(implib)
  #     endif()

  #     list(LENGTH implib nLibs)
  #     if("${nLibs}" GREATER 1)
  #       message(FATAL_ERROR "cannot handle implib nlibs greater 1")        
  #     endif()
  #     map_set("${implib}" "${cfg}" "${static_lib}")
  #   endif()


  # set(global GLOBAL)
  # set(linkage SHARED ) # STATIC, INTERFACE


  # if(NOT location AND NOT implib)
  #   set(linkage INTERFACE)  
  # else()


  # endif()

  # if(location) 
  #   set(linkage SHARED)
  # elseif(location )
  # endif()

  # add_library(${target_name} ${linkage} IMPORTED ${global})
  # target_set(${target_name} INTERFACE_INCLUDE_DIRECTORIES ${include_dirs})


  # if(implib)
  #   map_keys(${implib})
  #   ans(cfgs)
  #   foreach(cfg ${cfgs})
  #     map_tryget(${implib} ${cfg})
  #     ans(lib)
  #     target_set(${target_name} "IMPORTED_IMPLIB_${cfg}" "${lib}")
  #   endforeach()
  # endif()

  # if(location)
  #   map_keys(${location})
  #   ans(cfgs)
  #   foreach(cfg ${cfgs})
  #     map_tryget(${location} ${cfg})
  #     ans(loc)
  #     target_set(${target_name} "IMPORTED_LOCATION_${cfg}" "${loc}")
  #   endforeach()
  # endif()

  # return(${target_name})

endfunction()

